/*
 *  $Id: Lists.cs 1053 2010-05-19 10:05:23Z thenn.erannor $
 *	This file is a part of Ragima CCG.
 *	(C) 2008 Ragima development group.
 *
 *	Licensed under the terms of the GNU GPL License version 2.
 *
 */

using System;
using System.Collections;
using System.Collections.Generic;

namespace Ragima {
    /// <summary>
    /// Список объектов с приоритетом только одного объекта (отобранного по указанному условию)
    /// </summary>
    public class SingleSelectList<T> {
        private List<T> _list;
        private Comparison<T> _condition;

        public SingleSelectList(Comparison<T> condition) {
            _list = new List<T>();
            _condition = condition;
        }

        public bool Empty { get { return _list.Count == 0; } }
        public T Current { get { return _list.Count != 0 ? _list[0] : default(T); } }

        public void Clear() {
            _list.Clear();
        }
        public void Add(T item) {
            _list.Add(item);
            Sort();
        }
        public void Remove(T item) {
            _list.Remove(item);
            Sort();
        }
        private void Sort() {
            _list.Sort(_condition);
        }
    }

    /// <summary>
    /// Список объектов с проверкой их наличия по некоторому ключу
    /// </summary>
    public class KeyedList<K, T> {
        private List<T> _list;
        private Converter<T,K> _getter;

        public KeyedList(Converter<T,K> getter) {
            _list = new List<T>();
            _getter = getter;
        }

        public bool Contains(K key) {
            for (int i = 0; i < _list.Count; i++)
                if (object.Equals(key, _getter(_list[i])))
                    return true;
            return false;
        }

        public void ForEach(K key, Action<T> action) {
            if (action == null) return;
            for (int i = 0; i < _list.Count; i++)
                if (object.Equals(key, _getter(_list[i])))
                    action(_list[i]);
        }

        public void Clear() {
            _list.Clear();
        }
        public void Add(T item) {
            _list.Add(item);
        }
        public void Remove(T item) {
            _list.Remove(item);
        }
    }

    public class PriorityList<T>: ICollection<T> where T: IPrioritized {
        private List<T> _list;

        public PriorityList() {
            _list = new List<T>();
        }

        public int Count {
            get { return _list.Count; }
        }
        public bool IsReadOnly {
            get { return false; }
        }
        public void Add(T item) {
            for (int i = 0; i < _list.Count; i++) {
                if (_list[i].Priority > item.Priority) {
                    _list.Insert(i, item);
                    return;
                }
            }
            _list.Add(item);
        }
        public void Clear() {
            _list.Clear();
        }
        public bool Contains(T item) {
            return _list.Contains(item);
        }
        public void CopyTo(T[] array, int arrayIndex) {
            _list.CopyTo(array, arrayIndex);
        }
        public bool Remove(T item) {
            return _list.Remove(item);
        }
        IEnumerator IEnumerable.GetEnumerator() {
            return _list.GetEnumerator();
        }
        IEnumerator<T> IEnumerable<T>.GetEnumerator() {
            return _list.GetEnumerator();
        }
    }
}